﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.Threading.Tasks;
using System.Timers;
using EdexApiClient;
using IBS;
using CommerceML2IBS;

namespace EDEX2IBS
{
    public partial class Service1 : ServiceBase
    {
        private Timer timer = null;

        public Service1()
        {
            InitializeComponent();
            try
            {
                if (!EventLog.SourceExists(this.ServiceName + "_log"))
                    EventLog.CreateEventSource(this.ServiceName, this.ServiceName + "_log");
            }
            catch { }
            serviceLog.Source = this.ServiceName + "_log";
            serviceLog.Log = this.ServiceName + "_log";

        }

        protected override void OnStart(string[] args)
        {
            serviceLog.WriteEntry(this.ServiceName + " запущен");
            Properties.Settings.Default.Reload();
            var ExecuteTimes = Properties.Settings.Default.ExecuteTimes;
            if (Properties.Settings.Default.ExecuteImmediately)
                ExecuteTimes.Add(DateTime.Now.AddMinutes(1).ToString("HH:mm"));

            timer = new Timer();
            timer.Elapsed += new ElapsedEventHandler(OnElapsedTime);
            timer.Interval = TimerUtil.GetNewTimerInterval(ExecuteTimes);
            timer.Enabled = true;
        }

        protected override void OnStop()
        {
            serviceLog.WriteEntry(this.ServiceName + " остановлен");
            timer.Stop();
            timer.Close();
        }

        /// <summary>
        /// При срабатывании таймера
        /// </summary>
        /// <param name="source"></param>
        /// <param name="e"></param>
        private void OnElapsedTime(object source, ElapsedEventArgs e)
        {
            // Останавливаем таймей и стартуем выполнение выгрузки
            timer.Stop();
            Process();
            // Интервал таймера
            Properties.Settings.Default.Reload();
            timer.Interval = TimerUtil.GetNewTimerInterval(Properties.Settings.Default.ExecuteTimes);
            timer.Start();
        }

        private void Process()
        {
            try
            {
                serviceLog.WriteEntry("Запуск процедуры загрузки накладных");
                Properties.Settings.Default.Reload();
                string ApiURI = Properties.Settings.Default.ApiUri;
                string RootUri = Properties.Settings.Default.RootUri;
                string login = Properties.Settings.Default.LOGIN;
                string password = Properties.Settings.Default.PASSWORD;
                string PetrolKey = Properties.Settings.Default.PetrolKey;
                string TnkKey = Properties.Settings.Default.TNKKey;
                string IBSConnectionString = Properties.Settings.Default.IBSConnectionString;

                var edex = new EdexApiClient.EdexApiContext(ApiURI, RootUri, login, password);


                try
                {
                    serviceLog.WriteEntry("Выгрузка накладных по BP");
                    SendInvoice(edex, IBSConnectionString, PetrolKey);
                }
                catch (Exception ex)
                {
                    serviceLog.WriteEntry(ex.Message, EventLogEntryType.Error);
                }
                finally
                {
                    serviceLog.WriteEntry("Выгрузка накладных по BP завершена");
                }

                try
                {
                    serviceLog.WriteEntry("Выгрузка накладных по ТНК");
                    SendInvoice(edex, IBSConnectionString, TnkKey);
                }
                catch (Exception ex)
                {
                    serviceLog.WriteEntry(ex.Message, EventLogEntryType.Error);
                }
                finally
                {
                    serviceLog.WriteEntry("Выгрузка накладных по ТНК завершена");
                }
            }
            catch (Exception ex)
            {
                serviceLog.WriteEntry(ex.Message, EventLogEntryType.Error);
            }
            finally
            {
                serviceLog.WriteEntry("Процедура загрузки накладных завершена");
            }
        }

        private void SendInvoice(EdexApiClient.EdexApiContext edex, string connectionString, string companyKey)
        {
            /// Выбрать компанию
            edex.ChangeCompany(companyKey);

            /// Получить список новых накладных
            var invoices = edex.GetNewIncomingInvoices();

            invoices.ToList().ForEach(r =>
            {
                try
                {
                    /// Загрузить CommerceML
                    var stream = edex.GetIncomingInvoicesCommerceML(r.GUID_RECORD);
                    var xml = new System.IO.StreamReader(stream).ReadToEnd();

                    var context = new CommerceML2IBS.IntegrationContext(connectionString);

                    context.ProcessedDocument += ((sender, e) =>
                    {
                        serviceLog.WriteEntry("Загружен договор №" + e.DocumentNumber);
                        edex.SetIncomingNumber(e.Id, e.IncomingNumber);
                    });

                    context.Process(xml);
                }
                catch (Exception ex)
                {
                    serviceLog.WriteEntry(ex.Message, EventLogEntryType.Error);
                }
            });
        }
    }
}
